// This file is part of OpenMeca, an easy software to do mechanical simulation.
//
// Author(s)    :  - Damien ANDRE  <openmeca@gmail.com>
//
// Copyright (C) 2012 Damien ANDRE
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program.  If not, see <http://www.gnu.org/licenses/>.


#include "OpenMeca/Core/HistoricManager.hpp"
#include "OpenMeca/Core/System.hpp"

namespace OpenMeca
{
  namespace Core
  {
    
    HistoricManager::HistoricManager(System& system)
      :system_(system),
       archives_(),
       historicNavigator_()
    {
      Init();
    }

    HistoricManager::~HistoricManager()
    {
      
    }

    void
    HistoricManager::Init()
    {
      archives_.push_back(std::string());
      historicNavigator_ =  --archives_.end();
      system_.Save(*historicNavigator_);
    }

    
    void
    HistoricManager::SystemEdited()
    {
      std::cout << "HistoricManager::SystemEdited" << std::endl;
      if (IsInUndoRedoMode()==true)
	{
	  archives_.erase(++historicNavigator_, archives_.end());
	  std::cout << "Undo, Redo mode detected, erase obsolete archives" << std::endl;
	}
      archives_.push_back(std::string());
      historicNavigator_ =  --archives_.end();
      system_.Save(*historicNavigator_);
    }

    bool
    HistoricManager::IsInUndoRedoMode()
    {
      return (historicNavigator_ !=  --archives_.end());
    }

     void
    HistoricManager::LoadPreviousState()
    {
      assert(historicNavigator_ != archives_.begin());
      system_.Reset();
      --historicNavigator_;
      system_.Load(*historicNavigator_);
      system_.Update();
    }

    void
    HistoricManager::LoadNextState()
    {
      std::cout << "HistoricManager::LoadNextState" << std::endl;
      assert(historicNavigator_ != --archives_.end());
      system_.Reset();
      ++historicNavigator_;
      system_.Load(*historicNavigator_);
      system_.Update();
    }

    void 
    HistoricManager::Reset()
    {
      archives_.clear();
      Init();
    }


    bool
    HistoricManager::IsUndoPossible() const
    {
      assert(historicNavigator_ != archives_.end());
      return (historicNavigator_ != archives_.begin());
    }

    bool
    HistoricManager::IsRedoPossible() const
    {
      assert(historicNavigator_ != archives_.end());
      return (historicNavigator_ != --archives_.end());
    }

    bool
    HistoricManager::IsSystemEdited() const
    {
      return (archives_.size() > 1 && IsUndoPossible()==true);
    }
    
  }
}


